
/**
 * Universidad del Valle de Guatemala
 * CC2003 Algoritmos y Estructuras de Datos
 * Proyecto 1: Intérprete de LISP --> Lambda LISP
 * @version 2 Septiembre, 2009
 * Integrantes:
 *      @author Julio Chicas, José García, Ernesto Rodríguez, Karen Tojín
 **/
/**
 * Descripción: Clase auxiliar para definir las funciones mediante la instrucción DEFUN
 **/
import java.util.ArrayList;
import java.util.List;

public class Stored {

    private static VarArray var = new VarArray();
    private static ArrayList<Function> fun = new ArrayList<Function>(0);

    /**
     * Método que agrega una variable al Array
     * @param v: Variable a agregar
     */
    public static void addVar(Variable v) {
        var.add(v);
        int a = 0;
    }

    /**
     * Método que agrega una variable al Array
     * @param nom: Nombre de la variable
     * @param val: Valor de la variable
     */
    public static void addVar(String nom, Object val) {
        var.add(nom, val);
        int a = 0;
    }

    /**
     * Método que devuelve el Array con las variables
     * @return VarArray con las variables
     */
    public static VarArray getVar() {
        return var;
    }

    /**
     * Método para agregar una función al Array
     * @param a: La función a agregar
     */
    public static void addFun(Function a) {
        try {
            search(a.getName()).set(a.getOperands(), a.getFun());
        } catch (NonexistentException e) {
            fun.add(a);
        }
    }

    /**
     * Método para agregar una función al Array
     * @param name: Nombre de la función
     * @param operands: Operandos
     * @param function: Lo que la función realizará
     */
    public static void addFun(String name, List operands, List<String> function) {
        try {
            search(name).set(operands, function);
        } catch (NonexistentException e) {
            fun.add(new Function(name, operands, function));
        }
    }

    /**
     * Método que realiza una la evaluación de la función
     * @param function: Función a revisar
     * @param variable: Operandos de la función
     * @return La función si fue encontrada
     * @throws NonexistentException
     * @throws UnoperableException
     */
    public static Object evalFun(List function, VarArray variable) throws NonexistentException, UnoperableException {
        return search((String) function.remove(0)).evalFun(function, variable);
    }

    /**
     * Método que busca una función dentro del Array
     * @param name: Nombre de la función a buscar
     * @return La función si fue encontrada
     * @throws NonexistentException
     */
    private static Function search(String name) throws NonexistentException {
        for (int a = 0; a < fun.size(); a++) {
            if (fun.get(a).eq(name)) {
                return fun.get(a);
            }
        }
        throw new NonexistentException();
    }
}
